package secloud

import (
	"context"
	"errors"
	"github.com/antihax/optional"
	"github.com/astaxie/beego/validation"
)

type AuthEntrance struct {
	Base *BaseClient
}

func NewAuthEntrance() *AuthEntrance {
	return &AuthEntrance{
		Base: BaseSvc,
	}
}

type AuthOpts struct {
	ClientId     optional.String
	ClientSecret optional.String
}

// Token this func returns auth data, including accessToken and expires deadline
func (ae *AuthEntrance) Token(authOpts *AuthOpts) (*AuthClient, error) {
	valid := validation.Validation{}
	valid.MinSize(authOpts.ClientId.Value(), 1, "appKey").Message("请输入合法的AppKey")
	valid.MinSize(authOpts.ClientSecret.Value(), 1, "appSecret").Message("请输入合法的AppSecret")
	if valid.HasErrors() {
		return nil, handleValidationErrors(valid.Errors)
	}

	var ret AuthResp
	_, err := ae.Base.C.R().
		SetHeader("Content-Type", "application/json").
		SetQueryParams(map[string]string{
			"clientId":     authOpts.ClientId.Value(),
			"clientSecret": authOpts.ClientSecret.Value(),
		}).
		SetResult(&ret).
		Get("/auth/token")
	if err != nil {
		return nil, err
	}

	if ret.Code != 200 {
		return nil, errors.New(ret.Msg)
	}

	ctx := context.WithValue(context.Background(), ContextAccessToken, ret.Data.AccessToken)
	return &AuthClient{
		CipherClient: NewCipherClient(ctx),
		KmsClient:    NewKmsClient(ctx),
	}, nil
}
